package utils;

/**
 * @author: dm
 * @date: 2024/1/16 10:25
 * @description:
 */
public class DecimalConversionUtils {
    /**
     * 二进制转十进制
     * @param binary
     * @return
     */
    public static double binaryToDecimal(String binary) throws Exception {
        double res = 0L;
        if (binary != null) {
            for (int i = 0; i < binary.length(); i++) {
                if (binary.charAt(i) == '1') {
                    res += Math.pow(2, binary.length() - 1 - i);
                } else if (binary.charAt(i) == '0') {
                    continue;
                } else {
                    throw new Exception("非二进制字符串");
                }
            }
        }
        return res;
    }

    /**
     * 八进制转十进制
     * @param octal
     * @return
     */
    public static double octalToDecimal(String octal) throws Exception {
        double res = 0L;
        if (octal != null) {
            for (int i = 0; i < octal.length(); i++) {
                if (octal.charAt(i) < '8' && octal.charAt(i) > '0') {
                    res += (octal.charAt(i) - '0') * Math.pow(8, octal.length() - 1 - i);
                } else if (octal.charAt(i) == '0') {
                    continue;
                } else {
                    throw new Exception("非八进制字符串");
                }
            }
        }
        return res;
    }

    /**
     * 十六进制转十进制
     * @param hex
     * @return
     */
    public static double hexToDecimal(String hex) throws Exception {
        hex = hex.toUpperCase();
        double res = 0L;
        if (hex != null) {
            for (int i = 0; i < hex.length(); i++) {
                switch (hex.charAt(i)) {
                    case 'A':
                        res += 10 * Math.pow(16, hex.length() - 1 - i);
                        break;
                    case 'B':
                        res += 11 * Math.pow(16, hex.length() - 1 - i);
                        break;
                    case 'C':
                        res += 12 * Math.pow(16, hex.length() - 1 - i);
                        break;
                    case 'D':
                        res += 13 * Math.pow(16, hex.length() - 1 - i);
                        break;
                    case 'E':
                        res += 14 * Math.pow(16, hex.length() - 1 - i);
                        break;
                    case 'F':
                        res += 15 * Math.pow(16, hex.length() - 1 - i);
                        break;
                    default:
                        if (hex.charAt(i) >= '0' && hex.charAt(i) <= '9') {
                            res += (hex.charAt(i) - '0') * Math.pow(16, hex.length() - 1 - i);
                        } else {
                            throw new Exception("非十六进制字符串");
                        }
                }
            }
        }
        return res;
    }

    /**
     * @param decimal
     * @return 见给该数不断除以2，知道商为0为止，然后将每步得到的余数倒过来，就是对应的二进制
     * @throws Exception
     */
    public static String decimalToBinary(int decimal) {
        StringBuilder sb = new StringBuilder();
        while (decimal > 0) {
            int yv = decimal % 2;
            decimal /= 2;
            sb.insert(0, yv);
        }
        return sb.toString();
    }


    /**
     * @param decimal
     * @return 见给该数不断除以8，知道商为0为止，然后将每步得到的余数倒过来，就是对应的二进制
     * @throws Exception
     */
    public static String decimalToOctal(int decimal) {
        StringBuilder sb = new StringBuilder();
        while (decimal > 0) {
            int yv = decimal % 8;
            decimal /= 8;
            sb.insert(0, yv);
        }
        return sb.toString();
    }

    /**
     * @param decimal
     * @return 见给该数不断除以16，知道商为0为止，然后将每步得到的余数倒过来，就是对应的二进制
     * @throws Exception
     */
    public static String decimalToHex(int decimal) {
        StringBuilder sb = new StringBuilder();
        while (decimal > 0) {
            int yv = decimal % 16;
            decimal /= 16;
            switch (yv) {
                case 10:
                    sb.insert(0, 'A');
                    break;
                case 11:
                    sb.insert(0, 'B');
                    break;
                case 12:
                    sb.insert(0, 'C');
                    break;
                case 13:
                    sb.insert(0, 'D');
                    break;
                case 14:
                    sb.insert(0, 'E');
                    break;
                case 15:
                    sb.insert(0, 'F');
                    break;
                default:
                    sb.insert(0, yv);
            }
        }
        return sb.toString();
    }


}
